module Simapse
  module AssetFury
    module IsAsset
      module ActMethods
        # This is to be called in the asset class  (e.g : Asset -> is_asset :has_thumbs=>Image ) 
        # the option :has_thumbs tells which class holds the generated thumbs
        def is_asset(options={})
          options[:storage] ||= :file_system
          @@thumb_class = (t = options[:has_thumbs]) && (t.is_a?(Class) ? t : t.constantize)
          @@storage = Simapse::AssetFury::Storage.const_get options[:storage].to_s.classify
          @@storage_path = options[:storage_path] || "#{RAILS_ROOT}/downloads"
          has_many :thumbnails, :class_name=>options[:has_thumbs], :foreign_key=>'parent_id'
          options[:storage] ||=  :file_system
          extend ClassMethods
          include InstanceMethods
          include @@storage
          # Reminder : 
          #     before_save       before_save
          #     before_create    before_update
          #     INSERT              UPDATE
          #     after_create       after_update
          #     after_save          after_save
          # before_create/before_update -> same as before_save with new_record? check
          # NOTES for DEVELOPER
          # So the idea here is that the instance of an Asset must reflect its File state
          # wich are : name, content-type, size, width, height, and its thumbs.
          # As long as it is not modified, accessing the file is needless since all info is held by DB.
          # But if a save is involved we need a Temporary file to work on.
          before_save :before_save_process
          before_save :before_save_process
          after_save :after_save_process
        end
      end #ActsMethods
       
      module ClassMethods
      end # ClassMethods
    
      module InstanceMethods

        def current_file=(data)
          @current_file = Simapse::AssetFury::CurrentFile.new(data)
        end
        
        def current_file
          self.current_file=File.open(self.full_filename, 'rb') unless @current_file
          @current_file
        end
        
        # Keeps a referance of old_file 
        def filename=(new_name)
          current_file.filename = new_name if current_file.filename != new_name
          write_attribute :filename, current_file.filename
        end        
        
        def content_type=(content_type)
          write_attribute :content_type, content_type
        end
        
        # returns nil if it appears in a form
        def uploaded_data; nil; end
        
        # When a file is assigned to uploaded_data ->>
        # Simapse::File::TmpFile takes care of all the Tempfile durty stuff
        def uploaded_data=(data)
          self.current_file = data
          test_temp
        end
      
      private
        
        # Scenarios : 
        # *  new record : the Tempfile should already exist with uploaded_data
        # *  xisting record but uploaded_data has created a Tempfile
        # *  xisting record & uploaded_data : Tempfile must be pulled out from storage
        #
        # Tempfile : they vanishe when losing their scope (read in attachment_fu)
        # - Me : So how does one lose its scope ?
        # - Answer : in attachment_fu there's an array of them. They're out when Array's cleared.
        #   see -> temp_path=() & after_process_attachment
        #
        def before_save_process
          self.filename = current_file.filename
          self.content_type = current_file.content_type
          #~ self.size = current_file.size
        end
        
        def after_save_process
          save_to_storage
        end
        
        def initialize_default_thumbs
          @@thumb_class.options[:defaults].each do |suffix, size|
            self << @@thumb_class.new(options)
          end
        end
        
        
        def test_temp
          return unless @current_file
          logger.info "filename: #{@current_file.filename}"
          logger.info "path: #{@current_file.path}"
          logger.info "size: #{@current_file.size}"
          logger.info "content_type: #{@current_file.content_type}"
        end
        
      end # InstanceMethods
    end #HasAssets
  end #AssetFury
end #Simapse

  
